package com.logistics.service;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.logistics.common.Constants;
import com.logistics.common.SiteContextHolder;
import com.logistics.common.TenantContextHolder;
import com.logistics.dto.DriverCreateRequest;
import com.logistics.entity.Driver;
import com.logistics.entity.Site;
import com.logistics.mapper.DriverMapper;
import com.logistics.mapper.SiteMapper;
import jakarta.servlet.http.HttpServletRequest;
import org.springframework.stereotype.Service;
import org.springframework.util.StringUtils;
import org.springframework.web.context.request.RequestContextHolder;
import org.springframework.web.context.request.ServletRequestAttributes;

import java.util.List;

/**
 * 司机服务
 */
@Service
public class DriverService {
    
    private final DriverMapper driverMapper;
    private final SiteMapper siteMapper;
    
    public DriverService(DriverMapper driverMapper, SiteMapper siteMapper) {
        this.driverMapper = driverMapper;
        this.siteMapper = siteMapper;
    }
    
    /**
     * 创建司机
     */
    public Driver createDriver(DriverCreateRequest request) {
        Long tenantId = TenantContextHolder.getTenantId();
        Long siteId = request.getSiteId();
        
        // 确定站点ID：如果请求中指定了站点ID，使用指定的；否则使用当前用户的站点ID
        if (siteId == null) {
            siteId = SiteContextHolder.getSiteId();
        }
        
        if (siteId == null) {
            throw new RuntimeException("站点ID不能为空");
        }
        
        // 验证站点是否属于当前租户
        Site site = siteMapper.selectById(siteId);
        if (site == null || !site.getTenantId().equals(tenantId)) {
            throw new RuntimeException("站点不存在或不属于当前租户");
        }
        
        // 检查手机号是否重复（公司内唯一）
        LambdaQueryWrapper<Driver> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(Driver::getTenantId, tenantId)
               .eq(Driver::getPhone, request.getPhone());
        if (driverMapper.selectCount(wrapper) > 0) {
            throw new RuntimeException("手机号已存在");
        }
        
        // 检查身份证号是否重复（公司内唯一）
        wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(Driver::getTenantId, tenantId)
               .eq(Driver::getIdCard, request.getIdCard());
        if (driverMapper.selectCount(wrapper) > 0) {
            throw new RuntimeException("身份证号已存在");
        }
        
        // 生成工号（站点代码-SJ+流水号）
        String driverNo = generateDriverNo(siteId);
        
        Driver driver = new Driver();
        driver.setTenantId(tenantId);
        driver.setSiteId(siteId);
        driver.setDriverNo(driverNo);
        driver.setName(request.getName());
        driver.setGender(request.getGender());
        driver.setPhone(request.getPhone());
        driver.setIdCard(request.getIdCard());
        driver.setLicenseType(request.getLicenseType());
        driver.setLicenseNo(request.getLicenseNo());
        driver.setLicenseExpireDate(request.getLicenseExpireDate());
        driver.setEntryDate(request.getEntryDate());
        driver.setEmergencyContact(request.getEmergencyContact());
        driver.setEmergencyPhone(request.getEmergencyPhone());
        driver.setDriverStatus(request.getDriverStatus() != null ? request.getDriverStatus() : "IDLE");
        driver.setRemark(request.getRemark());
        
        driverMapper.insert(driver);
        
        return driver;
    }
    
    /**
     * 分页查询司机列表
     */
    public IPage<Driver> getDriverList(Integer current, Integer size, String driverStatus, String keyword, Long siteId) {
        Page<Driver> page = new Page<>(current, size);
        
        Long tenantId = TenantContextHolder.getTenantId();
        Long currentSiteId = SiteContextHolder.getSiteId();
        String role = getCurrentUserRole();
        
        LambdaQueryWrapper<Driver> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(Driver::getTenantId, tenantId);
        
        // 站点隔离逻辑
        if (Constants.Role.SUPER_ADMIN.equals(role)) {
            // 超级管理员和租户管理员：
            // 1. 如果前端传递了 siteId（选择了具体站点），按指定站点过滤
            // 2. 如果前端没有传递 siteId（选择了全部站点），显示所有站点的司机
            if (siteId != null) {
                wrapper.eq(Driver::getSiteId, siteId);
            }
            // siteId 为 null 时，不添加站点过滤条件，显示所有站点
        } else {
            // 普通用户（站点管理员、操作员等）：只能查看当前站点
            // 优先使用前端传递的 siteId，如果没有则使用上下文中的 currentSiteId
            Long effectiveSiteId = siteId != null ? siteId : currentSiteId;
            if (effectiveSiteId != null) {
                wrapper.eq(Driver::getSiteId, effectiveSiteId);
            } else {
                // 如果都没有站点ID，返回空结果
                wrapper.eq(Driver::getSiteId, -1L);
            }
        }
        
        if (StringUtils.hasText(driverStatus)) {
            wrapper.eq(Driver::getDriverStatus, driverStatus);
        }
        
        if (StringUtils.hasText(keyword)) {
            wrapper.and(w -> w
                .like(Driver::getName, keyword)
                .or()
                .like(Driver::getDriverNo, keyword)
                .or()
                .like(Driver::getPhone, keyword)
            );
        }
        
        wrapper.orderByDesc(Driver::getCreateTime);
        
        return driverMapper.selectPage(page, wrapper);
    }
    
    /**
     * 获取当前用户角色
     */
    private String getCurrentUserRole() {
        try {
            ServletRequestAttributes attributes = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
            if (attributes != null) {
                HttpServletRequest request = attributes.getRequest();
                Object roleObj = request.getAttribute("role");
                if (roleObj != null) {
                    return roleObj.toString();
                }
            }
        } catch (Exception e) {
            // 忽略异常
        }
        return null;
    }
    
    /**
     * 获取司机详情
     */
    public Driver getDriverById(Long id) {
        return driverMapper.selectById(id);
    }
    
    /**
     * 更新司机
     */
    public void updateDriver(Long id, DriverCreateRequest request) {
        Long tenantId = TenantContextHolder.getTenantId();
        Long currentSiteId = SiteContextHolder.getSiteId();
        String role = getCurrentUserRole();
        
        Driver driver = driverMapper.selectById(id);
        if (driver == null) {
            throw new RuntimeException("司机不存在");
        }
        
        // 权限检查：非超级管理员只能修改当前站点的司机
        if (!Constants.Role.SUPER_ADMIN.equals(role) && currentSiteId != null && !currentSiteId.equals(driver.getSiteId())) {
            throw new RuntimeException("无权修改其他站点的司机");
        }
        
        // 超级管理员可以修改站点归属
        if (Constants.Role.SUPER_ADMIN.equals(role) && request.getSiteId() != null) {
            Site site = siteMapper.selectById(request.getSiteId());
            if (site == null || !site.getTenantId().equals(tenantId)) {
                throw new RuntimeException("站点不存在或不属于当前租户");
            }
            driver.setSiteId(request.getSiteId());
        }
        
        driver.setName(request.getName());
        driver.setGender(request.getGender());
        driver.setPhone(request.getPhone());
        driver.setIdCard(request.getIdCard());
        driver.setLicenseType(request.getLicenseType());
        driver.setLicenseNo(request.getLicenseNo());
        driver.setLicenseExpireDate(request.getLicenseExpireDate());
        driver.setEntryDate(request.getEntryDate());
        driver.setEmergencyContact(request.getEmergencyContact());
        driver.setEmergencyPhone(request.getEmergencyPhone());
        driver.setDriverStatus(request.getDriverStatus());
        driver.setRemark(request.getRemark());
        
        driverMapper.updateById(driver);
    }
    
    /**
     * 删除司机
     */
    public void deleteDriver(Long id) {
        Long currentSiteId = SiteContextHolder.getSiteId();
        String role = getCurrentUserRole();
        
        Driver driver = driverMapper.selectById(id);
        if (driver == null) {
            throw new RuntimeException("司机不存在");
        }
        
        // 权限检查：非超级管理员只能删除当前站点的司机
        if (!Constants.Role.SUPER_ADMIN.equals(role) && currentSiteId != null && !currentSiteId.equals(driver.getSiteId())) {
            throw new RuntimeException("无权删除其他站点的司机");
        }
        
        driverMapper.deleteById(id);
    }
    
    /**
     * 生成司机工号
     * 格式：站点代码-SJ + 流水号（如：BJ-SJ000001）
     */
    private String generateDriverNo(Long siteId) {
        // 查询站点信息获取站点代码
        Site site = siteMapper.selectById(siteId);
        if (site == null) {
            throw new RuntimeException("站点不存在");
        }
        
        String siteCode = site.getSiteCode();
        if (siteCode == null || siteCode.isEmpty()) {
            throw new RuntimeException("站点代码为空");
        }
        
        // 查询该站点下已有司机数量，生成流水号
        LambdaQueryWrapper<Driver> wrapper = new LambdaQueryWrapper<>();
        wrapper.eq(Driver::getSiteId, siteId);
        long count = driverMapper.selectCount(wrapper);
        
        // 流水号从1开始，6位数字，不足补0
        String seqNum = String.format("%06d", count + 1);
        
        return siteCode.toUpperCase() + "-SJ" + seqNum;
    }
    
    /**
     * 更新司机状态
     */
    public void updateDriverStatus(Long driverId, String status) {
        Driver driver = driverMapper.selectById(driverId);
        if (driver != null) {
            driver.setDriverStatus(status);
            driverMapper.updateById(driver);
        }
    }
    
    /**
     * 根据司机的订单情况自动更新司机状态
     */
    public void updateDriverStatusByOrders(Long driverId) {
        // 查询司机当前有多少未完成的订单
        int activeOrderCount = driverMapper.countActiveOrdersByDriverId(driverId, TenantContextHolder.getTenantId());
        
        // 如果没有未完成的订单，设为空闲；否则设为忙碌
        String newStatus = activeOrderCount > 0 ? "BUSY" : "IDLE";
        updateDriverStatus(driverId, newStatus);
    }
    
    /**
     * 查询司机的所有订单（包括历史订单）
     */
    public List<?> getDriverOrders(Long driverId) {
        Long tenantId = TenantContextHolder.getTenantId();
        return driverMapper.selectOrdersByDriverId(driverId, tenantId);
    }
}

